using System.Collections;
using System.Collections.Generic;
using UnityEngine;

/// <summary>
/// Buff性能管理�?- 优化Buff系统的性能
/// </summary>
public class BuffPerformanceManager : MonoBehaviour
{
    private static BuffPerformanceManager m_Instance;
    public static BuffPerformanceManager Instance
    {
        get
        {
            if (m_Instance == null)
            {
                m_Instance = FindObjectOfType<BuffPerformanceManager>();
                if (m_Instance == null)
                {
                    GameObject go = new GameObject("BuffPerformanceManager");
                    m_Instance = go.AddComponent<BuffPerformanceManager>();
                }
            }
            return m_Instance;
        }
    }

    [Header("性能设置")]
    [Tooltip("最大同时存在的Buff数量")]
    public int maxActiveBuffs = 1000;
    
    [Tooltip("Buff更新频率（每帧更新多少个Buff�?")]
    public int buffsPerFrame = 10;
    
    [Tooltip("是否启用Buff批处�?")]
    public bool enableBatchProcessing = true;
    
    [Tooltip("是否启用对象�?")]
    public bool enableObjectPooling = true;

    /// <summary>
    /// 所有活跃的Buff队列
    /// </summary>
    private Queue<BuffBase> m_ActiveBuffs = new Queue<BuffBase>();
    
    /// <summary>
    /// 需要更新的Buff列表
    /// </summary>
    private List<BuffBase> m_BuffsToUpdate = new List<BuffBase>();
    
    /// <summary>
    /// 当前帧已更新的Buff数量
    /// </summary>
    private int m_CurrentFrameUpdateCount = 0;
    
    /// <summary>
    /// 性能统计相关
    /// </summary>
    private float m_TotalUpdateTime = 0f;
    private int m_UpdateFrameCount = 0;
    private float m_AverageUpdateTime = 0f;

    private void Awake()
    {
        if (m_Instance == null)
        {
            m_Instance = this;
            DontDestroyOnLoad(gameObject);
        }
        else if (m_Instance != this)
        {
            GameObject.Destroy(gameObject);
        }
    }

    private void Update()
    {
        if (enableBatchProcessing)
        {
            ProcessBuffsInBatches();
        }
    }

    /// <summary>
    /// 注册Buff到性能管理�?
    /// </summary>
    /// <param name="buff">要注册的Buff</param>
    public void RegisterBuff(BuffBase buff)
    {
        if (buff == null) return;
        
        // 检查是否超过最大数量限�?
        if (m_ActiveBuffs.Count >= maxActiveBuffs)
        {
            Logger.LogWarning("Buff数量超过限制，移除最旧的Buff");
            RemoveOldestBuff();
        }
        
        m_ActiveBuffs.Enqueue(buff);
        m_BuffsToUpdate.Add(buff);
    }

    /// <summary>
    /// 从性能管理器中移除Buff
    /// </summary>
    /// <param name="buff">要移除的Buff</param>
    public void UnregisterBuff(BuffBase buff)
    {
        if (buff == null) return;
        
        m_BuffsToUpdate.Remove(buff);
        
        // 从队列中移除（需要重新构建队列）
        var tempQueue = new Queue<BuffBase>();
        while (m_ActiveBuffs.Count > 0)
        {
            var currentBuff = m_ActiveBuffs.Dequeue();
            if (currentBuff != buff)
            {
                tempQueue.Enqueue(currentBuff);
            }
        }
        m_ActiveBuffs = tempQueue;
    }

    /// <summary>
    /// 批处理Buff更新
    /// </summary>
    private void ProcessBuffsInBatches()
    {
        float startTime = Time.realtimeSinceStartup;
        m_CurrentFrameUpdateCount = 0;
        
        for (int i = m_BuffsToUpdate.Count - 1; i >= 0; i--)
        {
            if (m_CurrentFrameUpdateCount >= buffsPerFrame)
                break;
            
            var buff = m_BuffsToUpdate[i];
            if (buff == null)
            {
                m_BuffsToUpdate.RemoveAt(i);
                continue;
            }
            
            // 更新Buff
            buff.Tick();
            m_CurrentFrameUpdateCount++;
            
            // 检查Buff是否已完�?
            if (buff.IsFinished())
            {
                m_BuffsToUpdate.RemoveAt(i);
            }
        }
        
        // 记录性能统计
        float updateTime = (Time.realtimeSinceStartup - startTime) * 1000f; // 转换为毫�?
        m_TotalUpdateTime += updateTime;
        m_UpdateFrameCount++;
        
        // 计算平均更新时间
        if (m_UpdateFrameCount > 0)
        {
            m_AverageUpdateTime = m_TotalUpdateTime / m_UpdateFrameCount;
        }
    }

    /// <summary>
    /// 移除最旧的Buff
    /// </summary>
    private void RemoveOldestBuff()
    {
        if (m_ActiveBuffs.Count > 0)
        {
            var oldestBuff = m_ActiveBuffs.Dequeue();
            if (oldestBuff != null)
            {
                oldestBuff.Cancel();
                m_BuffsToUpdate.Remove(oldestBuff);
            }
        }
    }

    /// <summary>
    /// 获取当前活跃Buff数量
    /// </summary>
    public int GetActiveBuffCount()
    {
        return m_ActiveBuffs.Count;
    }

    /// <summary>
    /// 清理所有Buff
    /// </summary>
    public void ClearAllBuffs()
    {
        while (m_ActiveBuffs.Count > 0)
        {
            var buff = m_ActiveBuffs.Dequeue();
            if (buff != null)
            {
                buff.Cancel();
            }
        }
        
        m_BuffsToUpdate.Clear();
    }

    /// <summary>
    /// 获取性能统计信息
    /// </summary>
    public BuffPerformanceStats GetPerformanceStats()
    {
        return new BuffPerformanceStats
        {
            activeBuffCount = m_ActiveBuffs.Count,
            buffsToUpdateCount = m_BuffsToUpdate.Count,
            currentFrameUpdateCount = m_CurrentFrameUpdateCount,
            maxActiveBuffs = maxActiveBuffs,
            buffsPerFrame = buffsPerFrame
        };
    }

    /// <summary>
    /// 获取平均更新时间（毫秒）
    /// </summary>
    public float GetAverageUpdateTime()
    {
        return m_AverageUpdateTime;
    }

    /// <summary>
    /// 获取内存使用量（MB�?
    /// </summary>
    public float GetMemoryUsage()
    {
        // 简单的内存估算
        long totalMemory = System.GC.GetTotalMemory(false);
        return totalMemory / (1024f * 1024f);
    }

    private void OnDestroy()
    {
        ClearAllBuffs();
    }
}

/// <summary>
/// Buff性能统计信息
/// </summary>
[System.Serializable]
public struct BuffPerformanceStats
{
    public int activeBuffCount;
    public int buffsToUpdateCount;
    public int currentFrameUpdateCount;
    public int maxActiveBuffs;
    public int buffsPerFrame;
}
